package cn.agiledata.bank.linkbank.impl.cib;

import java.math.BigDecimal;
import java.util.Date;

import cn.agiledata.bank.account.service.ISequenceGenerator;
import cn.agiledata.bank.common.util.DateUtil;
import cn.agiledata.bank.linkbank.impl.AbstractBankNetPayRequest;
import cn.agiledata.bank.linkbank.impl.AbstractBankPayRequest;
import cn.agiledata.bank.linkbank.logic.CryptoKeyValidator;
import cn.agiledata.bank.linkbank.logic.DigitalSignGeneratable;

/**
 * 中国兴业银行网上银行支付请求
 * 
 * @author 马贤波
 * 
 */
public final class CibNetPayRequest extends AbstractBankNetPayRequest implements
		DigitalSignGeneratable {
	private CibOrderIdTransformer orderIdTransformer;

	private CryptoKeyValidator cryptoKeyValidator;

	public CibNetPayRequest() {
		super();
		this.orderIdTransformer = new CibOrderIdTransformer();
		this.cryptoKeyValidator = new CibCryptoKeyValidator();
		init();
	}

	private void init() {
		setParameter(CibNetConstant.REQUEST_NOTIFY_TYPE,
				CibNetConstant.NOTIFY_TYPE_NOTIFY); // 商户通知类型：交易成功网上银行通知商户
		setParameter(CibNetConstant.REQUEST_PAY_METHOD,
				CibNetConstant.PAY_METHOD_IMMEDIATE);// 支付方式：立即支付
		setParameter(CibNetConstant.REQUEST_CURRENCY_TYPE,
				CibNetConstant.CURRENCY_TYPE_CNY);// 订单币种：人民币（CNY）
	}

	protected AbstractBankPayRequest getCopiedInstance() {
		CibNetPayRequest request = new CibNetPayRequest();
		request.orderIdTransformer = this.orderIdTransformer;
		request.cryptoKeyValidator = this.cryptoKeyValidator;
		return request;
	}

	public void setSequenceGenerator(ISequenceGenerator sequenceGenerator) {
		this.orderIdTransformer.setSequenceGenerator(sequenceGenerator);
	}

	public String getMerchantUrl() {
		return getParameter(CibNetConstant.REQUEST_MERCHANT_URL);
	}

	public void setMerchantUrl(String merchantUrl) {
		setParameter(CibNetConstant.REQUEST_MERCHANT_URL, merchantUrl);
	}

	public void setAmount(BigDecimal amount) {
		setParameter(CibNetConstant.REQUEST_AMOUNT, amount.setScale(2)
				.toString());
	}

	public void setDate(Date date) {
		String dateValue = DateUtil.date2String(date,
				CibNetConstant.DATE_FORMAT);
		setParameter(CibNetConstant.REQUEST_DATE, dateValue);
	}

	public void setMerchantId(String merchantId) {
		setParameter(CibNetConstant.REQUEST_MERCHANT_ID, merchantId);
	}

	public void setOrderId(String orderId) {
		setParameter(CibNetConstant.REQUEST_ORDER_ID, this.orderIdTransformer
				.transId2OrderId(orderId));
	}

	public String getCryptoKeyDescription() {
		return this.cryptoKeyValidator.getCryptoKeyDescription();
	}

	public boolean validateCryptoKey(String cryptoKey) {
		boolean valid = this.cryptoKeyValidator.validateCryptoKey(cryptoKey);
		this.setValid(valid);
		return valid;
	}

	public void setMac(String mac) {
		setParameter(CibNetConstant.REQUEST_MAC, mac);
	}

	public String generateDigitalSign(String cryptoKey) {
		String[] keys = { CibNetConstant.REQUEST_MERCHANT_ID,
				CibNetConstant.REQUEST_ORDER_ID, CibNetConstant.REQUEST_DATE,
				CibNetConstant.REQUEST_AMOUNT,
				CibNetConstant.REQUEST_NOTIFY_TYPE,
				CibNetConstant.REQUEST_CURRENCY_TYPE,
				CibNetConstant.REQUEST_MERCHANT_URL,
				CibNetConstant.REQUEST_PAY_METHOD };
		String mac = CibUtils.generateMac(getParameters(), keys, cryptoKey);
		setMac(mac);
		return mac;
	}

}
